package com.ctvit.cch.core.utils;

import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;

/**
 * 时间衰减工具类
 * 
 * 计算给定时间与当前时间的衰减值
 * 
 * @author heyingcheng
 * @date 2025/11/14
 */
public class TimeDecayUtils {

    // 半衰期30天
    private static final double HALF_LIFE_DAYS = 30.0;

    /**
     * 计算时间衰减因子 (0-1]
     * - 时间越新，衰减因子越接近1.0
     * - 24小时内的记录不会衰减（衰减因子=1.0）
     * - 超过24小时的记录按指数规律衰减
     * - 即使时间非常久远，衰减因子也不会低于0.1
     * - null值返回0.5（中等衰减）
     * 
     * @param createTime 创建时间
     * @return 衰减因子，越接近1表示越新
     */
    public static double calculateDecayFactor(LocalDateTime createTime) {
        if (createTime == null) {
            return 0.5;
        }

        // 计算小时差
        long hoursDiff = ChronoUnit.HOURS.between(createTime, LocalDateTime.now());

        // 24小时内不衰减
        if (hoursDiff <= 24) {
            return 1.0;
        }

        // 指数衰减：decay = e^(-λt)
        // λ = ln(2) / 半衰期
        double lambda = Math.log(2) / (HALF_LIFE_DAYS * 24);
        double decayFactor = Math.exp(-lambda * hoursDiff);

        // 保证最小值为0.1，避免过度衰减
        return Math.max(decayFactor, 0.1);
    }

    /**
     * 简化的线性衰减（备用方案）
     * 
     * @param createTime 创建时间
     * @return 衰减因子，越接近1表示越新
     */
    public static double calculateLinearDecay(LocalDateTime createTime) {
        long daysDiff = ChronoUnit.DAYS.between(createTime, LocalDateTime.now());
        // 每天衰减2%
        double factor = 1.0 - (daysDiff * 0.02);
        return Math.max(factor, 0.1);
    }

}
